package com.lamda.zhekou.dao.impl;


import com.lamda.zhekou.dao.GenericDao;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Repository;
import org.springframework.transaction.annotation.Transactional;

import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import java.lang.reflect.ParameterizedType;
import java.util.List;

/**
 * Created by MJiao on 9/1/14.
 */
@Repository
public class GenericDaoImpl<T> implements GenericDao<T> {


    @PersistenceContext
    protected EntityManager entityManager;

    @Transactional
    @Override
    public T persist(T entity) {
        this.entityManager.persist(entity);
        return entity;
    }

    @Transactional
    @Override
    public T update(T entity) {
        this.entityManager.merge(entity);
        return entity;
    }

    @Transactional
    @Override
    public void delete(Long id) {
        this.entityManager.remove(this.findById(id));

    }

    @Override
    public T findById(Long id) {
        Class<T> entityClass = (Class<T>) ((ParameterizedType) this.getClass().getGenericSuperclass()).getActualTypeArguments()[0];
        return this.entityManager.find(entityClass, id);
    }

    @Override
    public List<T> findAll() {
        Class<T> entityClass = (Class<T>) ((ParameterizedType) this.getClass().getGenericSuperclass()).getActualTypeArguments()[0];
        String JPQL = new StringBuilder("select entity from ").append(entityClass.getName()).append(" entity").toString();
        return this.entityManager.createQuery(JPQL).getResultList();
    }

    /**
     * 统计总的数据记录数
     *
     * @return
     */
    @Override
    public Long selectCount() {
        Class<T> entityClass = (Class<T>) ((ParameterizedType) this.getClass().getGenericSuperclass()).getActualTypeArguments()[0];

        StringBuilder JPQLStringBuilder = new StringBuilder("select count(entity.id) from ").append(entityClass.getName()).append(" entity  ");
        return (Long) this.entityManager.createQuery(JPQLStringBuilder.toString()).getSingleResult();
    }

    public T findByParameterAndSingleResult(String parameterKey, String parameterValue, String queryMethod) {
        Class<T> entityClass = (Class<T>) ((ParameterizedType) this.getClass().getGenericSuperclass()).getActualTypeArguments()[0];

        StringBuilder JPQLStringBuilder = new StringBuilder("select entity from ").append(entityClass.getName()).append(" entity  ");

        if (StringUtils.isEmpty(queryMethod) || (!queryMethod.equals(QueryParameterUtil.EQUAL) && !queryMethod.equals(QueryParameterUtil.LIKE))) {
            throw new RuntimeException("非法的查询类型:" + queryMethod);
        }
        JPQLStringBuilder.append("where entity.").append(parameterKey).append(queryMethod).append(":").append(parameterKey);
        try {
            return (T) this.entityManager.createQuery(JPQLStringBuilder.toString()).setParameter(parameterKey, parameterValue).getSingleResult();
        } catch (Exception e) {

        }
        return null;
    }



}